package me.helllp.book.concurrent.ch04;

import java.util.Random;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;

/**
 * 验证ThreadLocal的功能
 * 
 * @author Administrator
 *
 */
public class RandomTask implements Callable<Long>{
	//	产生随机数的数量
	public static final int GEN_COUNT = 10000000;
	
	//	产生线程的数量
	public static final int THREAD_COUNT = 4;
	
	//	构造线程池
	static ExecutorService exec = Executors.newFixedThreadPool(THREAD_COUNT);
	
	private static Random rnd = new Random(111);
	
	public static ThreadLocal<Random> threadRnd = new ThreadLocal<Random>(){
		protected Random initialValue() {
			return new Random(111);
		};
	};
	
	private int mode = 0;
	
	public RandomTask(int mode){
		this.mode = mode;
	}
	
	public Random getRandom(){
		if(this.mode == 0){
			return rnd;
		}else{
			return threadRnd.get();
		}
	}
	
	@Override
	public Long call() throws Exception {
		long b = System.currentTimeMillis();
		
		for(int i=0 ; i<GEN_COUNT; i++){
			getRandom().nextLong();
		}
		
		long e = System.currentTimeMillis();
		
		System.out.println(Thread.currentThread().getName() + " 执行消耗的时间：" + (e-b) + " 毫秒");
		
		return e-b;
	}
	
	public static void main(String[] args) throws InterruptedException, ExecutionException {
		@SuppressWarnings("unchecked")
		Future<Long>[] futs = new Future[THREAD_COUNT];
		
		for(int i=0; i<THREAD_COUNT; i++){
			futs[i] = (Future<Long>) exec.submit(new RandomTask(0));
		}
		
		long totalTime = 0;
		
		for(int i=0 ;i<THREAD_COUNT; i++){
			totalTime += futs[i].get();
		}
		
		System.out.println("共享一个Random的情况下，总耗时：" + totalTime);
		
		for(int i=0; i<THREAD_COUNT; i++){
			futs[i] = (Future<Long>) exec.submit(new RandomTask(1));
		}
		
		totalTime = 0;
		
		for(int i=0 ;i<THREAD_COUNT; i++){
			totalTime += futs[i].get();
		}
		
		System.out.println("使用ThreadLocal的情况下，总耗时：" + totalTime);
		
	}
}
